package cn.lysj.framework.common.validate.asp;

import cn.lysj.framework.common.utils.web.Resp;

import cn.lysj.framework.common.validate.Message;
import cn.lysj.framework.common.validate.annotation.Validator;
import cn.lysj.framework.common.validate.entity.Medusa;
import cn.lysj.framework.common.validate.exception.ValidatorException;
import lombok.extern.slf4j.Slf4j;
import org.aspectj.lang.JoinPoint;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Before;
import org.aspectj.lang.annotation.Pointcut;
import org.aspectj.lang.reflect.MethodSignature;
import org.springframework.context.annotation.Configuration;
import java.lang.reflect.Method;

/**
 * @author ww
 * @description
 * @create 2018-08-15 10:00
 **/
@Aspect  //一个切面
@Configuration  // spring boot 配置类
@Slf4j
public class RequestParamValidAspect {

    private Validator validator = null;

    /**
     * @author ww
     * @date 2018-08-22 9:39
     * @Description 拦截使用Validator注解
     */
    @Pointcut("@annotation(cn.lysj.framework.common.validate.annotation.Validator)")
    public void soaServiceBefore(){}

    /* * 通过连接点切入 */
    @Before("soaServiceBefore()")
    public void twiceAsOld1(JoinPoint point) {
        // 获得切入方法参数
        Object [] args = point.getArgs();
        //参数校验
        Medusa medusa = Message.getMsg(args[0],validator.value());
        //判断校验是否成功（不成功则抛出异常，抛出异常后会被@Around中的catch接收）
        if(!medusa.isFlag()){
            log.error("["+args[0].toString().split("\\(")[0]+"]"+medusa.getMessage());
            throw new ValidatorException(medusa.getMessage());
        }
    }

    /**
     * @author ww
     * @date 2018-08-17 13:42
     * @Description 环绕通知（在@before之前执行  中间是执行方法   在@After之后执行）这三步如果出错的话，都会进入到catch中
     */
    @Around(value = "soaServiceBefore()")
    public Object around(ProceedingJoinPoint proceedingJoinPoint) throws Throwable {
        //获取方法上的Validator注解
        MethodSignature methodSignature = (MethodSignature) proceedingJoinPoint.getSignature();
        Method method = methodSignature.getMethod();
        validator = method.getAnnotation(Validator.class);
        Object result = null;
        try {
            //用于方法执行
            result = proceedingJoinPoint.proceed();
        }catch (Exception e){
            ValidatorException errorMsgException = (ValidatorException) e;
            return new Resp(Resp.PARAM_ERROR,errorMsgException.getMessage());
        }
        return result;
    }
}
